package org.brisling.sysman.service;

import java.util.HashMap;
import java.util.List;

import org.brisling.authorize.shiro.PasswordSecurity;
import org.brisling.base.domain.ListDomain;
import org.brisling.base.domain.RetDomain;
import org.brisling.common.ConstSysParam;
import org.brisling.common.SysConfig;
import org.brisling.common.exception.UseridMustNotNullException;
import org.brisling.common.exception.WrongPasswordException;
import org.brisling.common.util.JsonUtil;
import org.brisling.common.util.LongUtil;

import org.brisling.sysman.domain.Users;
import org.brisling.sysman.repository.SecurityUsersRepo;
import org.brisling.sysman.service.base.BaseSysmanListByDeptService;

import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.servlet.ModelAndView;




@RestController
@RequestMapping("/user")
/**
 * 含用户密码、盐值等敏感信息的用戶后台服務service,
 * @Author : jackson wang
 * @Date   : 2015年6月8日 下午4:18:01
 * @Update : 2015年10月4日 下午12:43:00
 * @version: 1.0
 */
public class SecurityUserService extends BaseSysmanListByDeptService<Users>{
	
		
	@Autowired
	private SecurityUsersRepo baseRepo;
	
	public SecurityUserService(){
		this.moduleName = ConstSysParam.MODULE_USER;
	}

	/* (non-Javadoc)
	 * @see org.brisling.service.sysman.SecurityUserServiceInf#getMainPage()
	 */
	@RequestMapping("/mainPage.action")
	public ModelAndView getMainPage(){
		return this.getBizMainPage();
	}
	
	/* (non-Javadoc)
	 * @see org.brisling.service.sysman.SecurityUserServiceInf#getEditPage()
	 */
	@RequestMapping("/editPage.action")
	public ModelAndView getEditPage(){
		return this.getBizEditPage();
	}
	
	/* (non-Javadoc)
	 * @see org.brisling.service.sysman.SecurityUserServiceInf#getPasswordPage()
	 */
	@RequestMapping("/userPasswordPage.action")
	public ModelAndView getPasswordPage(){
		return new ModelAndView("/sysman/sysman_user/userPassword");
	}
	
	/* (non-Javadoc)
	 * @see org.brisling.service.sysman.SecurityUserServiceInf#getUserListDomain(java.lang.String, java.lang.String, java.lang.String, java.lang.String)
	 */
	@RequestMapping("/getListDomain.action")
	public ListDomain<Users> getUserListDomain(@RequestParam(value="deptid",required=false) String deptid,
			@RequestParam(value="page",required=false) String page,
			@RequestParam(value="rows",required=false) String rows,
			@RequestParam(value="sort",required=false) String sort){
		
		Integer _deptid = LongUtil.getIntValue(deptid, null);		
		
		ListDomain<Users> list = null;
		if(_deptid!=null){
			list = super.getPagedListDomainByDeptid(_deptid, page, rows);
		}else{
			list = super.getAllListDomain(page,rows,getSort(sort));
		}
		return list;
	}
	
	/* (non-Javadoc)
	 * @see org.brisling.service.sysman.SecurityUserServiceInf#getUserList(java.lang.String, java.lang.String, java.lang.String, java.lang.String)
	 */
	@RequestMapping("/getList.action")
	public List<Users> getUserList(@RequestParam(value="deptid",required=false) String deptid,
			@RequestParam(value="page",required=false) String page,
			@RequestParam(value="rows",required=false) String rows,
			@RequestParam(value="sort",required=false) String sort){
		
		Integer _deptid = LongUtil.getIntValue(deptid, null);		
		List<Users> list = null;
		if(_deptid!=null){
			list= super.getPagedListByDeptid(_deptid, page, rows,sort);
		}else{
			list = super.getAll(page,rows,getSort(sort));
		}
		return this.clearPasswordList(list);
	}
	
	/**
	 * 删除记录,单条或批量删除记录,id不为空，执行单条删除，id为空且ids不为空，执行批量删除
	 * @param id	待删除的单条记录id
	 * @param ids	待删除的多条记录id，以','分隔
	 * @return
	 */
	@RequestMapping("/del.action")
	public RetDomain delRow(@RequestParam(value="id",required=false) Long id,@RequestParam(value="ids",required=false) String ids){
				
		return super.delRows(id, ids);		 
	}
	
	
	/* (non-Javadoc)
	 * @see org.brisling.service.sysman.SecurityUserServiceInf#save(java.lang.String)
	 */
	@RequestMapping("/save.action")
	public Users save(@RequestBody String body){
		Users user = JsonUtil.bodyToObj(body, Users.class);
		if(user.getId()!=null){
			Users oldUser = super.getOne(user.getId());
			user.setPassword(oldUser.getPassword());
			user.setPassword_salt(oldUser.getPassword_salt());
			if(user.getIdentify()==null){
				user.setIdentify(user.getId().toString());
			}
		}
		super.save(user);
		//清除密码
		return this.clearPassword(user);
	}
	
	
	/* (non-Javadoc)
	 * @see org.brisling.service.sysman.SecurityUserServiceInf#save(org.brisling.domain.sysman.Users)
	 */
	@Override
	public Users save(Users vusr){
		Users user = new Users();
		if(vusr.getId()!=null){
			user = super.getOne(vusr.getId());					
		}
		//不覆盖密码
		BeanUtils.copyProperties(vusr, user,"password","password_salt");	
		super.save(user);
		return user;		
	}
	
	/* (non-Javadoc)
	 * @see org.brisling.service.sysman.SecurityUserServiceInf#savePassWord(java.lang.String)
	 */
	@SuppressWarnings("rawtypes")
	@RequestMapping("/securityUserPasswordReset.action")
	public RetDomain savePassWord(@RequestBody String body) throws UseridMustNotNullException, WrongPasswordException{
		
		HashMap map =  JsonUtil.bodyToObj(body, HashMap.class);
		
		String _id = map.get("id").toString();
		
		
		if((_id==null)||(_id.trim().length()<=0)){
			throw new UseridMustNotNullException();
		}
		
		String oldPassword = map.get("oldPassword").toString();
		String newPassword = map.get("newPassword").toString();
		
		//未配置密码重置项，调用本地密码设置方法
		return resetLocalPassword(_id,oldPassword,newPassword);		
		
	}
	
	/*
	 * 重置本地密码
	 */
	private RetDomain resetLocalPassword(String uid,String oPass,String nPass){		
		
		RetDomain r = RetDomain.errorDomain("密码修改失败");
		Long _uid = uid==null?null:Long.parseLong( uid);
		if(_uid!=null){
			
			boolean savePassword = false;	
			Users user = super.getOne(_uid);
			String _password = oPass==null?null:oPass.trim();
			
			if((user!=null)  && (user.getId()!=null)){
				//用户存在
				if((user.getPassword_salt()==null)||(user.getPassword_salt().trim().length()<=0)){
					//原密码为空
					savePassword = true;
				}else{
					//原密码不为空
					if(PasswordSecurity.authenticPassword(user, _password)){
						savePassword = true;
					}else{
						//原密码输入不正确
						r.setCode("-2");
						return r;
					}
				}
			}else{
				//用户不存在
				r.setCode("-1");
				return r;
			}
			
			if(savePassword){
				String sql = "update %1$s set password_salt='%2$s',password='%3$s' where id =%4$s";
				String _salt = PasswordSecurity.generateSalt();
				String _generatePassword = PasswordSecurity.getSecurityPassword(nPass, _uid, _salt).toString();
				sql = String.format(sql, this.moduleName,_salt,_generatePassword,_uid);
				
				int retNum =super.executeNativeDelOrUpdate(sql);
				if(retNum >0){
					r = RetDomain.successDomain("密码设置成功");
					r.setCode("1");					
					return r;
				}
			}
		}
		
		return r;
	}	
	
	
	/* (non-Javadoc)
	 * @see org.brisling.service.sysman.SecurityUserServiceInf#clearPasswordList(java.util.List)
	 */
	public List<Users> clearPasswordList(List<Users> users){
		if(users!=null&&users.size()>0){
			for(Users u:users){
				u.eraseCredentials();
			}
		}
		return users;
	}
	
	/* (non-Javadoc)
	 * @see org.brisling.service.sysman.SecurityUserServiceInf#clearPasswordListDomain(org.brisling.domain.base.impl.ListDomain)
	 */
	public ListDomain<Users> clearPasswordListDomain(ListDomain<Users> users){
		if(users!=null&&users.getRows()!=null){
			for(Users u:users.getRows()){
				u.eraseCredentials();
			}
		}
		return users;
	}
	
	/* (non-Javadoc)
	 * @see org.brisling.service.sysman.SecurityUserServiceInf#clearPassword(org.brisling.domain.sysman.Users)
	 */
	public Users clearPassword(Users usr){
		if((usr!=null)&&(usr.getId()!=null)){
			usr.eraseCredentials();
		}
		return usr;
	}
	
	/**
	 * 初始化密码
	 * @param id
	 * @return
	 */
	@RequestMapping("/initPwd.action")
	public RetDomain initPwd(@RequestParam(value="id",required=false) Long id){
		
		Users usr = this.getOne(id);
		if(usr !=null && usr.getId()!=null){
			String _salt = PasswordSecurity.generateSalt();
			String _generatePassword = PasswordSecurity.getSecurityPassword("123456", id, _salt).toString();
			
			usr.setPassword(_generatePassword);
			usr.setPassword_salt(_salt);
			save(usr);
			return RetDomain.successDomain("");
		}
		return RetDomain.errorDomain("");	 
	}
	
	public Users findByNameOrLoginName(String name){
		return baseRepo.findByNameOrLoginName(name,name);
	}
	
	public Users getOne(Long id){
		return baseRepo.findOne(id);
	}
	
}
